package com.zxp.juc.thread.threadPool;

import com.zxp.javaee.thread.MyTask01;
import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.RejectedExecutionException;
import java.util.concurrent.RejectedExecutionHandler;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

/**
 * 测试Executors的三种线程池区别
 *
 * @author zxp
 * @date 2021/8/13 11:56
 */
@Slf4j
public class TestExecutors {
    // cachedThreadPool 核心线程为0,非核心线程为最大,因此来一个任务就创建一个线程
    private static ExecutorService cachedThreadPool = Executors.newCachedThreadPool();
    private static ExecutorService fixedThreadPool = Executors.newFixedThreadPool(10);
    private static ExecutorService singleThreadPool = Executors.newSingleThreadExecutor();

    private static ExecutorService myThreadPool = new ThreadPoolExecutor(10, 20,
            0, TimeUnit.SECONDS, new LinkedBlockingQueue<>(20),
            new RejectedExecutionHandler() {
                @Override
                public void rejectedExecution(final Runnable r, final ThreadPoolExecutor e) {
                    try {
                        String msg = String.format("Thread pool is EXHAUSTED!" +
                                        " Pool Size: %d (active: %d, core: %d, max: %d, largest: %d), Task: %d (completed: %d)," +
                                        " Executor status:(isShutdown:%s, isTerminated:%s, isTerminating:%s)!",
                                e.getPoolSize(), e.getActiveCount(), e.getCorePoolSize(), e.getMaximumPoolSize(), e.getLargestPoolSize(),
                                e.getTaskCount(), e.getCompletedTaskCount(), e.isShutdown(), e.isTerminated(), e.isTerminating());
                        log.warn(msg);
                        if (!e.isShutdown()) {
                            r.run();
                        }
                    } catch (Throwable exception) {
                        throw new RejectedExecutionException("Failed to start a new thread", exception);
                    }
                }
            }

    );


    public static void main(String[] args) {
        long start = System.currentTimeMillis();

        for(int i = 1; i <= 100; i++) {
            //cachedThreadPool.execute( new MyTask01(i));
            //fixedThreadPool.execute( new MyTask01(i));
            //singleThreadPool.execute( new MyTask01(i));
            //myThreadPool.execute(new MyTask01(i));
            CompletableFuture.runAsync(new MyTask01(i), myThreadPool);
        }

        long end = System.currentTimeMillis();
        System.out.printf("运行时间：%d", end - start);
    }

}
